/*////////////////////////////////////////////////////////////////////////
*
*  Project:      mapgen
*  Description:  Map Generator for Planet Wars at http://ai-contest.com/.
*  Author:       Copyright (C) 2010 Alexander Makodzeba
*  License:      GPLv3
*
*  This file is part of mapgen.
*
*  mapgen is free software: you can redistribute it and/or modify
*  it under the terms of the GNU General Public License as published by
*  the Free Software Foundation, either version 3 of the License, or
*  (at your option) any later version.
*
*  mapgen is distributed in the hope that it will be useful,
*  but WITHOUT ANY WARRANTY; without even the implied warranty of
*  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
*  GNU General Public License for more details.
*
*  You should have received a copy of the GNU General Public License
*  along with mapgen.  If not, see <http://www.gnu.org/licenses/>.
*
////////////////////////////////////////////////////////////////////////*/

#include "StdAfx.h"
#include "MapGeneratorParams.h"

//////////////////////////////////////////////////////////////////////////
// parse object from string
template <class T> bool from_string(const std::string& s, T& t)
{
	std::istringstream iss(s);
	return !(iss >> t).fail();
}

//////////////////////////////////////////////////////////////////////////
// parse two objects of the same type from string
template <class T> bool from_string(const std::string& s, T& t1, T& t2)
{
	std::istringstream iss(s);
	char delimiter;
	return !(iss >> t1 >> delimiter >> t2).fail();
}

//////////////////////////////////////////////////////////////////////////
// helper function: parse pair of integers separated by "-"
bool ParseMinMax(char str[], int& n1, int& n2)
{
	bool bRet= from_string<int>(std::string(str), n1, n2);
	MinMaxNormalize<int>(n1, n2);
	return bRet;
}

//////////////////////////////////////////////////////////////////////////
// helper function: parse pair of doubles separated by ":"
bool ParsePoint(char str[], double& f1, double& f2)
{
	bool bRet= from_string<double>(std::string(str), f1, f2);
	return bRet;
}

//////////////////////////////////////////////////////////////////////////
// parse command line parameters
bool MapGeneratorParams::ParseCommandLine(int argc, char* argv[])
{
	bool bRet = true;

	//1 - map prefix, example: "map"
	mapFilePrefix = argv[1];

	//2 - total number of maps to generate, example: "100"
	bRet &= from_string<int>(std::string(argv[2]), mapsCount);
	//check
	if(mapsCount < 1) mapsCount = 1;

	//3 - generate symmetric map? example: "1" or "0"
	bRet &= from_string<bool>(std::string(argv[3]), generateSymmetricMap);

	//4 - count of players, example: "2"
	bRet &= from_string<int>(std::string(argv[4]), playersCount);
	//check
	if(playersCount < NUM_PLAYERS_MIN) playersCount = NUM_PLAYERS_MIN;
	if(playersCount > NUM_PLAYERS_MAX) playersCount = NUM_PLAYERS_MAX;

	//5 - player planet size, example: "5"
	bRet &= from_string<int>(std::string(argv[5]), playerPlanetSize);

	//6 - start population of player, example: "100"
	bRet &= from_string<int>(std::string(argv[6]), playerPlanetPopulation);
	//check
	if(playerPlanetPopulation < 1) playerPlanetPopulation = 1;

	//7 - planet size, example: "1-5"
	bRet &= ParseMinMax(argv[7], planetSize.Min, planetSize.Max);

	//8 - planet population, example: "0-150"
	bRet &= ParseMinMax(argv[8], planetPopulation.Min, planetPopulation.Max);

	//9 - planets count, example: "10-10"
	bRet &= ParseMinMax(argv[9], planetCount.Min, planetCount.Max);

	//10 - world top left point, example: "1.0:1.0"
	bRet &= ParsePoint(argv[10], pointWorldTopLeft.x, pointWorldTopLeft.y);

	//11 - world bottom right point, example: "30.0:30.0"
	bRet &= ParsePoint(argv[11], pointWorldBottomRight.x, pointWorldBottomRight.y);

	// calculate world center point
	MinMaxNormalize<double>(pointWorldTopLeft.x, pointWorldBottomRight.x);
	MinMaxNormalize<double>(pointWorldTopLeft.y, pointWorldBottomRight.y);

	// calculate world center point
	pointWorldCenter.x = (pointWorldBottomRight.x - pointWorldTopLeft.x) / 2.0;
	pointWorldCenter.y = (pointWorldBottomRight.y - pointWorldTopLeft.y) / 2.0;

	return bRet;
};
